const fs = require("fs");
const path = require("path");
const { app } = require("electron");
const logger = require("./logger");

// 默认配置
const defaultConfig = {
  expertInfo: {
    id: "default-user-1",
    userName: "专家1",
    userCode: "expert1",
  },
  serverInfo: {
    url: "http://172.17.13.13:8070",
  },
  frontInfo: {
    url: "http://172.17.13.13:8070/static/#",
  },
};

class ConfigManager {
  constructor() {
    // 使用用户数据目录
    const userDataPath = app ? app.getPath("userData") : process.env.APPDATA;
    // 配置文件路径指向用户数据目录
    this.configPath = path.join(userDataPath, "config", "app-config.json");
    // 备份文件路径
    this.backupPath = path.join(
      userDataPath,
      "config",
      "app-config.backup.json"
    );

    // 确保 config 目录存在
    this.ensureConfigDirectory();

    // 初始化配置
    this.initConfig();
  }

  // 深度合并配置，保留本地已有的值，只在缺少字段时使用默认值
  mergeConfigWithDefaults(localConfig, defaultConfig) {
    if (!localConfig || typeof localConfig !== "object") {
      return { ...defaultConfig };
    }

    const merged = {};

    // 处理所有默认配置的键
    for (const key in defaultConfig) {
      if (
        typeof defaultConfig[key] === "object" &&
        defaultConfig[key] !== null
      ) {
        // 如果是对象，递归合并
        merged[key] = this.mergeConfigWithDefaults(
          localConfig[key],
          defaultConfig[key]
        );
      } else {
        // 如果本地配置中存在该键，使用本地值，否则使用默认值
        merged[key] = localConfig.hasOwnProperty(key)
          ? localConfig[key]
          : defaultConfig[key];
      }
    }

    // 保留本地配置中额外的键（不在默认配置中的键）
    for (const key in localConfig) {
      if (!defaultConfig.hasOwnProperty(key)) {
        merged[key] = localConfig[key];
      }
    }

    return merged;
  }

  // 确保配置目录存在
  ensureConfigDirectory() {
    try {
      const configDir = path.dirname(this.configPath);
      if (!fs.existsSync(configDir)) {
        fs.mkdirSync(configDir, { recursive: true });
        logger.info("Config---Created config directory:", configDir);
      }
    } catch (error) {
      logger.error("Config---Error creating config directory:", error);
    }
  }

  // 初始化配置
  initConfig() {
    try {
      // 加载或创建配置
      this.config = this.loadConfig();

      // 保存配置（确保文件存在）
      this.saveConfig();

      logger.info("Config---Configuration initialized successfully");
    } catch (error) {
      logger.error("Config---Error initializing config:", error);
      // 使用默认配置作为后备
      this.config = { ...defaultConfig };
    }
  }

  // 加载配置文件
  loadConfig() {
    try {
      if (fs.existsSync(this.configPath)) {
        const data = fs.readFileSync(this.configPath, "utf8");

        try {
          const config = JSON.parse(data);

          // 验证配置结构
          if (this.validateConfigStructure(config)) {
            // 合并配置，保留本地已有的值，只在缺少字段时使用默认值
            return this.mergeConfigWithDefaults(config, defaultConfig);
          } else {
            logger.error(
              "Config---Invalid config structure, attempting backup recovery"
            );
            return this.loadFromBackup();
          }
        } catch (parseError) {
          logger.error(
            "Config---JSON parse error, attempting backup recovery:",
            parseError
          );
          return this.loadFromBackup();
        }
      }

      // 如果文件不存在，返回默认配置
      logger.info(
        "Config---Config file not found, using default configuration"
      );
      return { ...defaultConfig };
    } catch (error) {
      logger.error("Config---Error loading config:", error);
      // 尝试从备份恢复
      return this.loadFromBackup();
    }
  }

  // 验证配置结构
  validateConfigStructure(config) {
    return (
      config &&
      typeof config === "object" &&
      config.expertInfo &&
      typeof config.expertInfo === "object" &&
      config.serverInfo &&
      typeof config.serverInfo === "object" &&
      config.frontInfo &&
      typeof config.frontInfo === "object"
    );
  }

  // 从备份文件加载配置
  loadFromBackup() {
    try {
      if (fs.existsSync(this.backupPath)) {
        logger.info("Config---Attempting to load from backup file");
        const backupData = fs.readFileSync(this.backupPath, "utf8");
        const backupConfig = JSON.parse(backupData);

        if (this.validateConfigStructure(backupConfig)) {
          logger.info("Config---Successfully loaded from backup");
          // 恢复主配置文件
          this.restoreFromBackup();
          return this.mergeConfigWithDefaults(backupConfig, defaultConfig);
        } else {
          logger.error("Config---Backup file is also corrupted");
        }
      } else {
        logger.warn("Config---No backup file found");
      }
    } catch (error) {
      logger.error("Config---Error loading from backup:", error);
    }

    // 最后的后备方案
    logger.warn("Config---Using default configuration as last resort");
    return { ...defaultConfig };
  }

  // 从备份恢复主配置文件
  restoreFromBackup() {
    try {
      if (fs.existsSync(this.backupPath)) {
        fs.copyFileSync(this.backupPath, this.configPath);
        logger.info("Config---Main config file restored from backup");
      }
    } catch (error) {
      logger.error("Config---Error restoring from backup:", error);
    }
  }

  // 保存配置文件
  saveConfig() {
    try {
      // 验证要保存的配置
      if (!this.validateConfigStructure(this.config)) {
        logger.error("Config---Cannot save invalid config structure");
        return false;
      }

      const configData = JSON.stringify(this.config, null, 2);

      // 创建备份（如果主配置文件存在且有效）
      this.createBackup();

      // 原子性写入：先写入临时文件，然后重命名
      const tempPath = this.configPath + ".tmp";
      fs.writeFileSync(tempPath, configData, "utf8");

      // 验证临时文件是否有效
      try {
        const tempData = fs.readFileSync(tempPath, "utf8");
        const tempConfig = JSON.parse(tempData);
        if (!this.validateConfigStructure(tempConfig)) {
          fs.unlinkSync(tempPath); // 删除无效的临时文件
          logger.error("Config---Generated config file is invalid");
          return false;
        }
      } catch (validateError) {
        fs.unlinkSync(tempPath); // 删除无效的临时文件
        logger.error(
          "Config---Failed to validate generated config:",
          validateError
        );
        return false;
      }

      // 重命名临时文件为主配置文件
      fs.renameSync(tempPath, this.configPath);
      logger.info("Config---Configuration saved successfully");
      return true;
    } catch (error) {
      logger.error("Config---Error saving config:", error);
      return false;
    }
  }

  // 创建配置备份
  createBackup() {
    try {
      if (fs.existsSync(this.configPath)) {
        const currentData = fs.readFileSync(this.configPath, "utf8");

        // 验证当前配置是否有效
        try {
          const currentConfig = JSON.parse(currentData);
          if (this.validateConfigStructure(currentConfig)) {
            fs.writeFileSync(this.backupPath, currentData, "utf8");
            logger.info("Config---Backup created successfully");
          } else {
            logger.warn("Config---Current config is invalid, skipping backup");
          }
        } catch (error) {
          logger.warn("Config---Current config is corrupted, skipping backup");
        }
      }
    } catch (error) {
      logger.error("Config---Error creating backup:", error);
    }
  }

  // 获取配置
  getConfig() {
    return this.config;
  }

  // 更新整个配置
  updateConfig(newConfig) {
    try {
      // 验证输入数据
      if (!this.validateConfigStructure(newConfig)) {
        logger.error("Config---Invalid config structure provided");
        return false;
      }

      // 备份当前配置
      const backupConfig = JSON.parse(JSON.stringify(this.config));

      // 更新配置，保留现有配置中已有的值
      this.config = this.mergeConfigWithDefaults(newConfig, defaultConfig);

      const success = this.saveConfig();
      if (success) {
        logger.info("Config---Configuration updated successfully");
        return true;
      } else {
        // 保存失败，回滚配置
        this.config = backupConfig;
        logger.error("Config---Failed to save config, changes rolled back");
        return false;
      }
    } catch (error) {
      logger.error("Config---Error updating config:", error);
      return false;
    }
  }

  // 重置配置为默认值
  resetConfig() {
    try {
      this.config = { ...defaultConfig };

      const success = this.saveConfig();
      if (success) {
        logger.info("Config---Configuration reset to default values");
      }
      return success;
    } catch (error) {
      logger.error("Config---Error resetting config:", error);
      return false;
    }
  }

  // 获取配置文件路径
  getConfigPath() {
    return this.configPath;
  }

  // 获取备份文件路径
  getBackupPath() {
    return this.backupPath;
  }

  // 检查配置是否有效
  isValidConfig() {
    try {
      return (
        this.config &&
        this.config.expertInfo &&
        typeof this.config.expertInfo === "object" &&
        this.config.serverInfo &&
        typeof this.config.serverInfo === "object" &&
        this.config.frontInfo &&
        typeof this.config.frontInfo === "object"
      );
    } catch (error) {
      logger.error("Config---Error validating config:", error);
      return false;
    }
  }

  // 手动创建备份
  manualBackup() {
    try {
      this.createBackup();
      return fs.existsSync(this.backupPath);
    } catch (error) {
      logger.error("Config---Error creating manual backup:", error);
      return false;
    }
  }

  // 手动从备份恢复
  manualRestore() {
    try {
      if (!fs.existsSync(this.backupPath)) {
        logger.error("Config---No backup file exists");
        return false;
      }

      const backupData = fs.readFileSync(this.backupPath, "utf8");
      const backupConfig = JSON.parse(backupData);

      if (!this.validateConfigStructure(backupConfig)) {
        logger.error("Config---Backup file is corrupted");
        return false;
      }

      // 备份当前配置
      const currentBackup = JSON.parse(JSON.stringify(this.config));

      // 更新内存中的配置，保留备份配置中已有的值
      this.config = this.mergeConfigWithDefaults(backupConfig, defaultConfig);

      // 保存配置
      const success = this.saveConfig();
      if (success) {
        logger.info("Config---Successfully restored from backup");
        return true;
      } else {
        // 恢复失败，回滚
        this.config = currentBackup;
        logger.error("Config---Failed to restore from backup, rolled back");
        return false;
      }
    } catch (error) {
      logger.error("Config---Error restoring from backup:", error);
      return false;
    }
  }

  // 检查备份文件是否存在且有效
  isBackupValid() {
    try {
      if (!fs.existsSync(this.backupPath)) {
        return false;
      }

      const backupData = fs.readFileSync(this.backupPath, "utf8");
      const backupConfig = JSON.parse(backupData);
      return this.validateConfigStructure(backupConfig);
    } catch (error) {
      logger.error("Config---Error validating backup:", error);
      return false;
    }
  }

  // 获取配置状态信息
  getConfigStatus() {
    return {
      configExists: fs.existsSync(this.configPath),
      backupExists: fs.existsSync(this.backupPath),
      configValid: this.isValidConfig(),
      backupValid: this.isBackupValid(),
      configPath: this.configPath,
      backupPath: this.backupPath,
    };
  }

  // 便捷的访问方法
  getExpertInfo() {
    return this.config.expertInfo;
  }

  getServerInfo() {
    return this.config.serverInfo;
  }

  getFrontInfo() {
    return this.config.frontInfo;
  }

  // 便捷的更新方法
  updateExpertInfo(expertInfo) {
    return this.updateConfig({
      ...this.config,
      expertInfo: { ...this.config.expertInfo, ...expertInfo },
    });
  }

  updateServerInfo(serverInfo) {
    return this.updateConfig({
      ...this.config,
      serverInfo: { ...this.config.serverInfo, ...serverInfo },
    });
  }

  updateFrontInfo(frontInfo) {
    return this.updateConfig({
      ...this.config,
      frontInfo: { ...this.config.frontInfo, ...frontInfo },
    });
  }
}

// 创建单例实例
const configManager = new ConfigManager();
module.exports = configManager;
